package org.reos.ReParser;

import java.util.ArrayList;
import java.util.TreeMap;

public abstract class Section implements ISection {
    public static ISection getInstance(String sectionName) {
        SectionNames sectionId = identifySection(sectionName);
        if (sectionId != null) {
            switch (sectionId) {
                case SYSTEM:
                    return new SystemSection(sectionName);
                case TARGET:
                    return new TargetSection(sectionName);
                case RTOS:
                    return new RTOSSection(sectionName);
            }
        }
        PartialSectionNames sectionId2 = identifySectionWithId(sectionName);
        if (sectionId2 == null) {
            return null;
        }
        switch (sectionId2) {
            case ISR:
                return new ISRSection(sectionName);
            case TASK:
                return new TaskSection(sectionName);
            case EVENT:
                return new EventSection(sectionName);
            case MESSAGE:
                return new MessageSection(sectionName);
            case QUEUE:
                return new QueueSection(sectionName);
            case TIMER:
                return new TimerSection(sectionName);
        }
        return null;
    }

    public static String parseSectionName(String str) {
        if (str == null) {
            return null;
        }
        for (SectionNames section : SectionNames.values()) {
            if (section.toString().equals(str.toUpperCase())) {
                return section.toString();
            }
        }

        String[] tmp = str.split(":");
        if (tmp.length < 2){
            return null;
        }
        if (tmp[1].trim().endsWith("]") == false) {
            return null;
        }
        for (PartialSectionNames section : PartialSectionNames.values()) {
            if (section.toString().equals(tmp[0].trim())) {
                return str;
            }
        }
        return null;
    }

    enum SectionNames {
		SYSTEM("[SYSTEM]"), TARGET("[TARGET]"), RTOS("[RTOS]");
		private String sectionId;
		private SectionNames(String sectionId) {
			this.sectionId = sectionId;
		}
		@Override
		public String toString() {
			return this.sectionId; 
		}
	}

    enum PartialSectionNames {
        ISR("[ISR"), TASK("[TASK"), EVENT("[EVENT"), MESSAGE("[MESSAGE"), QUEUE("[QUEUE"), TIMER("[TIMER");
        private String sectionId;
        private PartialSectionNames(String sectionId) {
            this.sectionId = sectionId;
        }
        @Override
        public String toString() {
            return this.sectionId;
        }
    }

    private static SectionNames identifySection(String sectionName) {
        for (SectionNames section : SectionNames.values()) {
            if (section.toString().equals(sectionName)) {
                return section;
            }
        }
        return null;
    }

    private static PartialSectionNames identifySectionWithId(String sectionName) {
        for (PartialSectionNames section : PartialSectionNames.values()) {
            if (sectionName.contains(section.toString())) {
                return section;
            }
        }

        return null;
    }
	
	protected String sectionName;
	protected TreeMap<String, String> sectionAttributes = new TreeMap<String, String>();
	
	protected Section(String sectionName) {
		this.sectionName = sectionName;
	}

	public String getSectionName() {
		return sectionName;
	}
	public void setSectionName(String sectionName) {
		this.sectionName = sectionName;
	}

    public ISection getSectionWithName(SectionNames sectionName, ArrayList<ISection> sectionData) {
        for (ISection section : sectionData) {
            if (section.getSectionName().startsWith(sectionName.toString())){
                return section;
            }
        }
        return null;
    }

    @Override
    public String getAttributeValue(String key) {
        return sectionAttributes.get(key);
    }

    @Override
    public boolean checkIntegrity() {
        // default implementation for sections without attributes
        return true;
    }

    @Override
    public boolean checkDependency(ArrayList<ISection> configData) {
        // default implementation for sections without dependecies
        return true;
    }
}
